<template>
	<el-form
		class="mg-6"
		ref="formRef"
		size="default"
		v-bind="widgetFormConfig"
		:model="formMod"
		status-icon
		disabled
		@keyup.enter.native="handleEnterSubmit"
	>
		<draggable
			v-model="componentList"
			tag="div"
			:gutter="20"
			class="el-row content"
			item-key="id"
			chosen-class="chosen"
			drag-class="drag-class"
			animation="300"
			:group="{ name: 'component' }"
			@end="onEnd"
		>
			<template #header>
				<div class="empty-box" v-if="componentList.length == 0">请从左侧列表中选择一个组件, 然后用鼠标拖动组件放置于此处</div>
			</template>
			<template #item="{ element, index }">
				<el-col :span="+element.option.span || 24" @click="componentIndex = index">
					<div :class="componentIndex == index ? 'item-content chosen' : 'item-content'">
						<el-form-item
							:prop="element.option.prop"
							:rules="element.option.display == false ? [] : element.option.rules"
							:style="{ display: 'flex', flexFlow: element.option.labelPosition == 'top' ? 'column' : 'row' }"
						>
							<template #label>
								<div class="flex align-center">
									<span>{{ element.option.label }}</span>
									<div>
										<el-tooltip effect="dark" v-if="element.option.tip" :content="element.option.tip" placement="top">
											<icon-info theme="outline" />
										</el-tooltip>
									</div>
								</div>
							</template>
							<component
								style="width: 100%; pointer-events: none"
								:is="typeComm[element.option.type] || ElInput"
								:disabled="true"
								:fileLabel="element.option.propName"
								v-model="formMod[element.option.prop]"
								v-model:modelName="formMod[element.option.propName]"
								v-bind="element.option"
								:placeholder="`请输入${element.option.label}`"
							>
								<template v-slot:prepend v-if="element.option.prepend">
									<span class="f14"> {{ element.option.prepend }}</span>
								</template>
								<template v-slot:append v-if="element.option.append">
									<span class="f14"> {{ element.option.append }}</span>
								</template>
								<optionPage v-if="element.option.dicData" :type="element.option.type" :dicData="element.option.dicData"> </optionPage>
							</component>
						</el-form-item>
					</div>
				</el-col>
			</template>
		</draggable>
		<el-row :gutter="20">
			<el-col :span="widgetFormConfig.inline ? 6 : 24" v-if="widgetFormConfig.showBtn" :xs="24">
				<el-form-item>
					<div class="fc w-100">
						<el-button type="primary" :disabled="loading" @click="onSubmit()">
							<el-icon class="mr4">
								<icon-search v-if="widgetFormConfig.inline" theme="outline" />
								<icon-check-one v-else theme="outline" />
							</el-icon>

							{{ widgetFormConfig.inline ? '搜索' : widgetFormConfig.submitBtnText }}
						</el-button>
						<el-button class="ap-btn" v-if="widgetFormConfig.showReset" @click="onReset(formRef)">
							<el-icon class="mr4">
								<icon-redo theme="outline" />
							</el-icon>
							{{ widgetFormConfig.inline ? '重置' : widgetFormConfig.backBtnText }}
						</el-button>
					</div>
				</el-form-item>
			</el-col>
		</el-row>
	</el-form>
</template>

<script lang="ts" setup>
import optionPage from '@/components/AplidCrud/src/AplidForm/option.vue'
import { getComponentCollecte } from '@/components/AplidCrud/hooks/index'
import { ElInput } from 'element-plus'
import { storeToRefs } from 'pinia'
import draggable from 'vuedraggable'
import { useDesign } from '@/stores/design'
import type { FormInstance } from 'element-plus'

const { componentIndex, componentList, widgetFormConfig } = storeToRefs(useDesign())
const typeComm: Object = getComponentCollecte()
const emit = defineEmits(['submit', 'reset', 'change'])
const formRef: any = ref<FormInstance>()
const loading = ref(false)
let formMod = ref({})

const onEnd = (e) => {
	componentIndex.value = e.newDraggableIndex
}
const onSubmit = () => {
	formRef.value.validate((valid) => {
		if (valid) {
			loading.value = true
			emit('submit', formMod.value, () => {
				loading.value = false
			})
		} else {
			loading.value = false
		}
	})
}
const onReset = () => {
	loading.value = false
	formMod.value = {}
	if (!formRef.value) return
	formRef.value.resetFields()
	emit('reset', formMod.value)
}
const handleEnterSubmit = () => {
	if (widgetFormConfig.value.showBtn) {
		onSubmit()
	}
}

defineExpose({
	onReset,
	onSubmit,
})
</script>

<style scoped lang="scss">
:deep(.el-input__wrapper) {
	width: 100%;
}

.chosen {
	position: relative;
	&::before {
		content: '';
		position: absolute;
		top: 0;
		left: 0;
		width: 100%;
		height: 100%;
		border: 2pt solid #0188fb;
	}
	&::after {
		content: '✣';
		position: absolute;
		top: 1px;
		left: 2px;
		width: 32px;
		height: 32px;
		background: #1890ff;
		color: #fff;
	}
}
.drag-class {
	background-color: #0186fb4c;
}
.widget-layout {
	position: absolute;
	width: 100%;
	height: 100%;
	top: 0;
	left: 0;
}

.empty-box {
	width: 100%;
	height: 80vh;
	display: flex;
	justify-content: center;
	align-items: center;
	color: #9cafc1;
}

.content {
	width: 100%;
}

.item-content {
	padding: 10px;
}

.item-content:hover {
	cursor: pointer;
}

.active {
	position: relative;
	&::before {
		content: '';
		position: absolute;
		top: 0;
		left: 0;
		width: 100%;
		height: 100%;
		border: 2pt solid #0188fb;
	}
	&::after {
		content: '✣';
		position: absolute;
		top: 1px;
		left: 2px;
		width: 32px;
		height: 32px;
		background: #1890ff;
		color: #fff;
	}
}
</style>
